home *** CD-ROM | disk | FTP | other *** search
/ BBS in a Box 4 / BBS in a Box - Macintosh - Volume IV (January 1992) (BBS in a Box).iso / Files / Prog / T / TransDisplay2p.cpt / EventLog.p next >
Encoding:
Text File  |  1988-12-09  |  19.2 KB  |  906 lines  |  [TEXT/PJMM]

  1. {    EventLog - TransDisplay event-logging demonstration program}
  2.  
  3. {    The project should include EventLog.p (this file), TransDisplay.p}
  4. {    (or a library made from TransDisplay.p), TransSkel.p (or a library}
  5. {    made from TransSkel.ps), and Runtime.lib and Interface.lib.  Also, you'll}
  6. {    need to set the run options to use the file EventLog.proj.rsrc as a resource}
  7. {    file. }
  8.  
  9. {    8 November 1986    Paul DuBois}
  10.  
  11. {11 January 1987    Ported to LightSpeed Pascal by Owen Hartnett    }
  12. {Ωhm Software Co., 163 Richard Drive, Tiverton, RI 02878        }
  13.  
  14. program EventLog;
  15.  
  16.     uses
  17. {$IFC UNDEFINED THINK_PASCAL}
  18.         Memtypes, Quickdraw, OSIntf, ToolIntf, PackIntf, 
  19. {$ENDC}
  20.         TransSkel, TransDisplay;
  21.  
  22.     const
  23.  
  24.                     { declare zoom box part codes }
  25.  
  26.         inZoomIN = 7;
  27.         inZoomOut = 8;
  28.  
  29.         maxButton = 14;
  30.  
  31.         helpTextRes = 1000;        { help text resource number }
  32.         aboutAlrtRes = 1000;    { About... alert resource number }
  33.  
  34.                     { Menu resource numbers }
  35.  
  36.         fileMenuRes = 1000;
  37.         editMenuRes = 1001;
  38.         logMenuRes = 1002;
  39.  
  40.                     { Window resource numbers }
  41.  
  42.         LogWindRes = 1000;
  43.         helpWindRes = 1001;
  44.         SelectWindRes = 1002;
  45.  
  46.             { File menu item numbers }
  47.  
  48.         showLog = 1;    { make windows visible/bring to front }
  49.         showHelp = 2;
  50.         ShowSelect = 3;
  51.         quit = 5;
  52.  
  53.                 { Edit menu item numbers }
  54.  
  55.         undo = 1;
  56.         cut = 3;
  57.         copy = 4;
  58.         paste = 5;
  59.         clear = 6;
  60.  
  61.                 { Log menu item numbers }
  62.  
  63.         logEvents = 1;        { whether events are logged }
  64.         excludeLWind = 2;
  65.         flushLog = 4;                { flush log output }
  66.         wrapStyle = 6;            { word wrap or not }
  67.         leftJust = 8;                { justification }
  68.         centerJust = 9;
  69.         rightJust = 10;
  70.         small = 12;                { text size }
  71.         medium = 13;
  72.         large = 14;
  73.         top = 16;                    { scroll home }
  74.         bottom = 17;                { scroll to bottom }
  75.  
  76.     type
  77.         booleanPtr = ^Boolean;
  78.         CtrlInfoPtr = ^CtrlInfoRec;
  79.         CtrlInfoRec = record
  80.                 loc: Point;        { upper left of control }
  81.                 title: Str255;        { control title }
  82.                 flagAddr: booleanPtr;    { associated boolean }
  83.                 ctrl: ControlHandle;        { associated control }
  84.                 subInfo: CtrlInfoPtr;    { subsidiary control }
  85.             end;
  86.  
  87.  
  88.     var
  89.         selectWind, helpWind, logWind: WindowPtr;
  90.             { event selection window }
  91.             { help text window }
  92.             { log output window }
  93.         fileMenu, editMenu, logMenu: MenuHandle;
  94.         reportEvents, excludeLog: Boolean;
  95.         { report events or not }
  96.         { exclude log window events or not }
  97.         logFont, logSize: integer;
  98.         logWrap, logJust: integer;
  99.         rMouseDown, rMouseMods, rMouseWind, rMouseLoc: Boolean;
  100.                             { event type selection flags }
  101.         rMousePart, rMouseSys, rMouseUp, rKeyDown, rKDMods: Boolean;
  102.         rAutoKey, rAKMods, rUpdate, rActivate, rDisk: Boolean;
  103.         currentPort: GrafPtr;
  104.  
  105. {    Control information.  The last field is used to tell which controls}
  106. {    are "owned" by another.  When the owner is unchecked, all the owned}
  107. {    controls go dim.}
  108.  
  109.         ctrlInfo: array[0..maxButton] of CtrlInfoRec;
  110.  
  111. {    Window that was in front last time checked    }
  112.  
  113.         lastFront: WindowPtr;
  114.         h: Handle;
  115.         dummy: Boolean;
  116.  
  117. {    Do in Pascal what can be done in C as static initializations.  }
  118.  
  119.     procedure setupStuff;
  120.  
  121.     begin
  122.         rMouseDown := true;
  123.         rMouseMods := false;
  124.         rMouseWind := true;
  125.         rMouseLoc := false;
  126.         rMousePart := true;
  127.         rMouseSys := false;
  128.         rMouseUP := false;
  129.         rKeyDown := true;
  130.         rKDMods := false;
  131.         rAutoKey := true;
  132.         rAKMods := false;
  133.         rUpdate := true;
  134.         rActivate := true;
  135.         rDisk := true;
  136.  
  137.         with ctrlInfo[0] do
  138.             begin
  139.                 loc.v := 5;
  140.                 loc.h := 10;
  141.                 title := 'Mouse Down';
  142.                 flagAddr := @rMouseDown;
  143.                 ctrl := nil;
  144.                 subInfo := nil;
  145.             end;
  146.  
  147.         with ctrlInfo[1] do
  148.             begin
  149.                 loc.v := 25;
  150.                 loc.h := 30;
  151.                 title := 'Modifiers';
  152.                 flagAddr := @rMouseMods;
  153.                 ctrl := nil;
  154.                 subInfo := @ctrlInfo[0];
  155.             end;
  156.  
  157.         with ctrlInfo[2] do
  158.             begin
  159.                 loc.v := 45;
  160.                 loc.h := 30;
  161.                 title := 'Window';
  162.                 flagAddr := @rMouseWind;
  163.                 ctrl := nil;
  164.                 subInfo := @ctrlInfo[0];
  165.             end;
  166.  
  167.         with ctrlInfo[3] do
  168.             begin
  169.                 loc.v := 65;
  170.                 loc.h := 30;
  171.                 title := 'Location';
  172.                 flagAddr := @rMouseLoc;
  173.                 ctrl := nil;
  174.                 subInfo := @ctrlInfo[0];
  175.             end;
  176.  
  177.         with ctrlInfo[4] do
  178.             begin
  179.                 loc.v := 85;
  180.                 loc.h := 30;
  181.                 title := 'Part Code';
  182.                 flagAddr := @rMousePart;
  183.                 ctrl := nil;
  184.                 subInfo := @ctrlInfo[0];
  185.             end;
  186.  
  187.         with ctrlInfo[5] do
  188.             begin
  189.                 loc.v := 105;
  190.                 loc.h := 30;
  191.                 title := 'System Clicks';
  192.                 flagAddr := @rMouseSys;
  193.                 ctrl := nil;
  194.                 subInfo := @ctrlInfo[0];
  195.             end;
  196.  
  197.         with ctrlInfo[6] do
  198.             begin
  199.                 loc.v := 125;
  200.                 loc.h := 10;
  201.                 title := 'Mouse Up';
  202.                 flagAddr := @rMouseUp;
  203.                 ctrl := nil;
  204.                 subInfo := nil;
  205.             end;
  206.  
  207.         with ctrlInfo[7] do
  208.             begin
  209.                 loc.v := 5;
  210.                 loc.h := 160;
  211.                 title := 'Key Down';
  212.                 flagAddr := @rKeyDown;
  213.                 ctrl := nil;
  214.                 subInfo := nil;
  215.             end;
  216.  
  217.         with ctrlInfo[8] do
  218.             begin
  219.                 loc.v := 25;
  220.                 loc.h := 180;
  221.                 title := 'Modifiers';
  222.                 flagAddr := @rKDMods;
  223.                 ctrl := nil;
  224.                 subInfo := @ctrlInfo[7];
  225.             end;
  226.  
  227.         with ctrlInfo[9] do
  228.             begin
  229.                 loc.v := 45;
  230.                 loc.h := 180;
  231.                 title := 'AutoKey';
  232.                 flagAddr := @rAutoKey;
  233.                 ctrl := nil;
  234.                 subInfo := nil;
  235.             end;
  236.  
  237.         with ctrlInfo[10] do
  238.             begin
  239.                 loc.v := 65;
  240.                 loc.h := 180;
  241.                 title := 'Modifiers';
  242.                 flagAddr := @rAKMods;
  243.                 ctrl := nil;
  244.                 subInfo := @ctrlInfo[9];
  245.             end;
  246.  
  247.         with ctrlInfo[11] do
  248.             begin
  249.                 loc.v := 85;
  250.                 loc.h := 160;
  251.                 title := 'Update';
  252.                 flagAddr := @rUpdate;
  253.                 ctrl := nil;
  254.                 subInfo := nil;
  255.             end;
  256.  
  257.         with ctrlInfo[12] do
  258.             begin
  259.                 loc.v := 105;
  260.                 loc.h := 160;
  261.                 title := 'Activate';
  262.                 flagAddr := @rActivate;
  263.                 ctrl := nil;
  264.                 subInfo := nil;
  265.             end;
  266.  
  267.         with ctrlInfo[13] do
  268.             begin
  269.                 loc.v := 125;
  270.                 loc.h := 160;
  271.                 title := 'Disk';
  272.                 flagAddr := @rDisk;
  273.                 ctrl := nil;
  274.                 subInfo := nil;
  275.             end;
  276.  
  277.         lastFront := nil;
  278.     end;
  279.  
  280. {    Print information about a window.  If it's a window with a title,}
  281. {    print the title.  Print whether it's a}
  282. {    desk accessory window.}
  283.  
  284.     procedure WindowInfo (theWind: WindowPeek);
  285.  
  286.         var
  287.             title: Str255;
  288.  
  289.     begin
  290.         GetWTitle(WindowPtr(theWind), title);
  291.         if length(title) > 0 then            { window has title }
  292.             begin
  293.                 DisplayChar(' ');
  294.                 DisplayString(title);
  295.             end;
  296.         if theWind^.windowKind < 0 then
  297.             DisplayString(' (DA)');
  298.     end;
  299.  
  300.     procedure Modifiers (mods: integer);
  301.  
  302.     begin
  303.         DisplayString(' mods ($');
  304.         DisplayHexInt(mods);
  305.         DisplayChar(')');
  306.     end;
  307.  
  308.     procedure MouseLoc (thePt: Point; thePort: GrafPtr);
  309.  
  310.         var
  311.             savePort: GrafPtr;
  312.  
  313.     begin
  314.         GetPort(savePort);
  315.         SetPort(thePort);
  316.         GlobalToLocal(thePt);
  317.         SetPort(savePort);
  318.         if rMouseLoc then
  319.             begin
  320.                 DisplaySTring(' loc (');
  321.                 DisplayInt(thePt.h);
  322.                 DisplayString(', ');
  323.                 DisplayInt(thePt.v);
  324.                 DisplayChar(')');
  325.             end;
  326.     end;
  327.  
  328. {    Mouse click.  Get the window that the click occurred in, and the}
  329. {    part of the window.}
  330.  
  331. {    Make sure to get all the part codes!  (incl. zoom box stuff)}
  332.  
  333.     procedure ReportMouse (theEvent: EventRecord);
  334.  
  335.         var
  336.             evtPt: Point;
  337.             evtpart: integer;
  338.             evtport: GrafPtr;
  339.  
  340.     begin
  341.         evtPt := theEvent.where;
  342.         evtPart := FindWindow(evtPt, evtPort);
  343.         if not excludeLog or (evtPort <> logWind) then
  344.             begin
  345.                 DisplayString('Mouse Click');
  346.                 case evtPart of
  347.                     inSysWindow: 
  348.  
  349. {    Click in a desk accessory window.}
  350.  
  351.                         if rMouseSys then
  352.                             begin
  353.                                 if rMousePart then
  354.                                     DisplayString(' in system window:');
  355.                                 if rMouseWind then
  356.                                     WindowInfo(WindowPeek(evtPort));
  357.                                 MouseLoc(evtPt, evtport);
  358.                             end;
  359.                     inDesk: 
  360.  
  361. {    Click in desk top.}
  362.  
  363.                         if rMousePart then
  364.                             DisplayString(' in desktop');
  365.                     inMenuBar: 
  366.  
  367. {    Click in menu bar.}
  368.  
  369.                         if rMousePart then
  370.                             DisplayString(' in menu bar');
  371.                     inGrow: 
  372.  
  373. {    Click in grow box.}
  374.  
  375.                         begin
  376.                             if rMousePart then
  377.                                 DisplayString(' in grow region:');
  378.                             if rMouseWind then
  379.                                 WindowInfo(WindowPeek(evtPort));
  380.                             MouseLoc(evtPt, evtPort);
  381.                         end;
  382.                     inDrag: 
  383.  
  384. {    Click in title bar.}
  385.  
  386.                         begin
  387.                             if rMousePart then
  388.                                 DisplayString(' in drag region:');
  389.                             if rMouseWind then
  390.                                 WindowInfo(WindowPeek(evtPort));
  391.                         end;
  392.                     inGoAway: 
  393.  
  394. {    Click in close box.}
  395.  
  396.                         begin
  397.                             if rMousePart then
  398.                                 DisplayString(' in close box:');
  399.                             if rMouseWind then
  400.                                 WindowInfo(WindowPeek(evtPort));
  401.                         end;
  402.                     inZoomIn: 
  403.  
  404. {    Click in zoom-in box.}
  405.  
  406.                         begin
  407.                             if rMousePart then
  408.                                 DisplayString(' in zoom-in box:');
  409.                             if rMouseWind then
  410.                                 WindowInfo(WindowPeek(evtPort));
  411.                         end;
  412.                     inZoomOut: 
  413.  
  414. {    Click in zoom-out box.}
  415.  
  416.                         begin
  417.                             if rMousePart then
  418.                                 DisplayString(' in zoom-out box:');
  419.                             if rMouseWind then
  420.                                 WindowInfo(WindowPeek(evtPort));
  421.                         end;
  422.                     inContent: 
  423.  
  424. {    Click in content region.}
  425.  
  426. {    (Might also check in in control, and if so, print control information)}
  427.  
  428.                         begin
  429.                             if rMousePart then
  430.                                 DisplayString(' in content region:');
  431.                             if rMouseWind then
  432.                                 WindowInfo(WindowPeek(evtPort));
  433.                             MouseLoc(evtPt, evtPort);
  434.                         end;
  435.                     otherwise
  436.                 end;
  437.                 if rMouseMods then
  438.                     Modifiers(theEvent.modifiers);
  439.                 DisplayLn;
  440.             end;
  441.     end;
  442.  
  443.     procedure ReportKey (what: integer; c: char; mods: integer; modFlag: Boolean);
  444.     begin
  445.         if what = keyDown then
  446.             DisplayString('Key Down: char "')
  447.         else
  448.             DisplayString('Autokey: char"');
  449.         DisplayChar(c);
  450.         DisplayString('" ');
  451.         if modFlag then
  452.             Modifiers(mods);
  453.         Displayln;
  454.     end;
  455.  
  456.     procedure ReportActivate (theWind: WindowPtr; mods: integer);
  457.  
  458.     begin
  459.         if BitAnd(mods, activeFlag) <> 0 then
  460.             DisplayString('Activate:')
  461.         else
  462.             DisplayString('Deactivate:');
  463.         WindowInfo(WindowPeek(theWind));
  464.         DisplayLn;
  465.     end;
  466.  
  467.     procedure ReportUpdate (theWind: WindowPtr);
  468.  
  469.     begin
  470.         DisplayString('Update:');
  471.         WindowInfo(WindowPeek(theWind));
  472.         Displayln;
  473.     end;
  474.  
  475. {    General event logger}
  476.  
  477.     function Logevent (theEvt: EventRecord): Boolean;
  478.  
  479.         var
  480.             theEvent: EventRecord;
  481.             evtPt: Point;
  482.             evtPort: GrafPtr;
  483.             evtpart: integer;
  484.             evtChar: char;
  485.             evtMods: integer;
  486.             r: Rect;
  487.  
  488.     begin
  489.         if reportEvents = false then
  490.             logevent := false
  491.         else
  492.             begin
  493.                 theEvent := theEvt;
  494.                 evtPt := theEvent.where;
  495.                 case theEvent.what of
  496.                     mouseDown: 
  497.  
  498. {    Mouse click.}
  499.  
  500.                         if rMouseDown then
  501.                             ReportMouse(theEvent);
  502.                     mouseUp: 
  503.                         if rMouseUP then
  504.                             begin
  505.                                 DisplayString('Mouse Up');
  506.                                 Displayln;
  507.                             end;
  508.                     keyDown: 
  509.  
  510. {    Key event.}
  511.  
  512.                         if not (excludeLog and (FrontWindow = logWind)) then
  513.                             if rKeyDown then
  514.                                 begin
  515.                                     evtChar := char(BitAnd(theEvent.message, charCodeMask));
  516.                                     evtMods := theEvent.modifiers;
  517.                                     ReportKey(keyDown, evtChar, evtMods, rKDMods);
  518.                                 end;
  519.                     autoKey: 
  520.                         if not (excludeLog and (FrontWindow = logWind)) then
  521.                             if rKeyDown then
  522.                                 begin
  523.                                     evtChar := char(BitAnd(theEvent.message, charCodeMask));
  524.                                     evtMods := theEvent.modifiers;
  525.                                     ReportKey(keyDown, evtChar, evtMods, rKDMods);
  526.                                 end;
  527.                     updateEvt: 
  528.  
  529. {    Update a window.  If it's an update for the log window, invalidate}
  530. {    it, because the message is written and will cause a scroll BEFORE}
  531. {    the window actually gets updated.  This means that part of what}
  532. {    needs redrawing will be scrolled out of the update region and won't}
  533. {    be redrawn properly.  Invalidating the entire port is wasteful but}
  534. {    makes sure the whole window can be drawn properly.}
  535.  
  536.                         begin
  537.                             if WindowPtr(theEvent.message) = logWind then
  538.                                 begin
  539.                                     SetPort(logWind);
  540.                                     InvalRect(logWind^.portRect);
  541.                                 end;
  542.                             if not (excludeLog and (WindowPtr(theEvent.message) = logWind)) then
  543.                                 if rUpdate then
  544.                                     begin
  545.                                         ReportUpdate(WindowPtr(theEvent.message));
  546.                                     end;
  547.                         end;
  548.                     activateEvt: 
  549.  
  550. {    Activate or deactivate a window.}
  551.  
  552.                         if not (excludeLog and (WindowPtr(theEvent.message) = logWind)) then
  553.                             if rActivate then
  554.                                 begin
  555.                                     ReportActivate(WindowPtr(theEvent.message), theEvent.modifiers);
  556.                                 end;
  557.                     diskEvt: 
  558.  
  559. {    handle inserts of uninitialized disks}
  560.  
  561.                         if rDisk then
  562.                             begin
  563.                                 DisplayString('Disk insertion');
  564.                                 if HiWord(theEvent.message) <> noErr then
  565.                                     DisplayString(' (needs initializing)');
  566.                                 Displayln;
  567.                             end;
  568.                     otherwise
  569.                 end;
  570.                 logEvent := false;
  571.             end;
  572.     end;
  573.  
  574. {    Background procedure.  Check front window, reset edit menu if window}
  575. {    changes from an application window to a non-application window.}
  576. {    Disable the Edit menu whenever an application window is active,}
  577. {    enable it otherwise.}
  578. {    Also called whenever it is known that the active window has changed.}
  579.  
  580.     procedure CheckFront;
  581.  
  582.         var
  583.             curWind: WindowPtr;
  584.             theKind: integer;
  585.             lastIsApp, curIsApp: Boolean;
  586.             mypeek: WindowPeek;
  587.  
  588.     begin
  589.         curIsApp := false;
  590.         lastIsApp := false;
  591.         curWind := frontwindow;
  592.         if (IsDWindow(lastFront)) or (lastFront = selectWind) then
  593.             lastIsApp := true;
  594.         if (IsDWindow(curWind)) or (curWind = selectWind) then
  595.             curIsApp := true;
  596.         if lastFront <> curWind then
  597.             begin
  598.                 if (IsDWindow(lastFront)) or (lastFront = selectWind) then
  599.                     lastIsApp := true;
  600.                 if (IsDWindow(curWind)) or (curWind = selectWind) then
  601.                     curIsApp := true;
  602.                 if lastIsApp <> curIsApp then
  603.                     begin
  604.                         theKind := 0;
  605.                         if curWind <> nil then
  606.                             begin
  607.                                 mypeek := windowpeek(curWind);
  608.                                 theKind := mypeek^.windowKind;
  609.                             end;
  610.                         if (curWind = nil) or (theKind < 0) then    { no window or DA in front }
  611.                             EnableItem(editMenu, 0)
  612.                         else
  613.                             DisableItem(editMenu, 0);
  614.                         DrawMenuBar;
  615.                     end;
  616.                 lastFront := curWind;
  617.             end;
  618.     end;
  619.  
  620. { ------------------------------------------------------------ }
  621. {            Event Selection Window Handler Routines                }
  622. { ------------------------------------------------------------ }
  623.  
  624.  
  625.  
  626. {    Activate event procedure for both display windows and the checkbox}
  627. {    window.}
  628.  
  629.     procedure Activate (active: Boolean);
  630.  
  631.     begin
  632.         CheckFront;
  633.     end;
  634.  
  635. {    Update window.  This is easy, just draw the controls.}
  636.  
  637.     procedure Update (resized: Boolean);
  638.  
  639.     begin
  640.         DrawControls(selectwind);
  641.         getPort(currentPort);
  642.     end;
  643.  
  644. {    Handle hits in check boxes:}
  645. {    Toggle check box, sync the associated flag, and enable or disable}
  646. {    any subsidiary check boxes accordingly.  (Subsidiaries have}
  647. {    information in the control structure that points back to the owner}
  648. {    check box.)}
  649.  
  650.     procedure Mouse (thePt: Point; t: longint; mods: integer);
  651.  
  652.         var
  653.             ctl: ControlHandle;
  654.             ci: CtrlInfoPtr;
  655.             val: boolean;
  656.             i: integer;
  657.             genericPtr: BooleanPtr;
  658.  
  659.     begin
  660.         if FindControl(thePt, selectWind, ctl) <> 0 then
  661.             if TrackControl(ctl, thePt, nil) <> 0 then
  662.                 begin
  663.                     ci := CtrlInfoPtr(GetCRefcon(ctl));
  664.                     val := not (GetCtlValue(ctl) <> 0);
  665.                     genericPtr := BooleanPtr(ci^.flagAddr);
  666.                     genericPtr^ := val;
  667.                     SetCtlValue(ctl, integer(val));
  668.  
  669.             { enable/disable any subsidiaries }
  670.  
  671.                     for i := 0 to maxButton - 1 do
  672.                         if ctrlInfo[i].subinfo <> nil then
  673.                             if ctrlInfo[i].subInfo^.ctrl = ci^.ctrl then
  674.                                 if val then
  675.                                     HiliteControl(ctrlInfo[i].ctrl, 0)
  676.                                 else
  677.                                     HiliteControl(ctrlInfo[i].ctrl, 255);
  678.                 end
  679.     end;
  680.  
  681. {    File menu handler}
  682.  
  683.     procedure DoFileMenu (item: integer);
  684.  
  685.     begin
  686.         case item of
  687.             showHelp: 
  688.                 begin
  689.                     SelectWindow(helpWind);
  690.                     ShowWindow(helpWind);
  691.                 end;
  692.             showSelect: 
  693.                 begin
  694.                     SelectWindow(selectWind);
  695.                     ShowWindow(selectWind);
  696.                 end;
  697.             showLog: 
  698.                 begin
  699.                     SelectWindow(logWind);
  700.                     ShowWindow(logWind);
  701.                 end;
  702.             quit: 
  703.                 SkelWhoa;
  704.             otherwise
  705.         end;
  706.     end;
  707.  
  708. {    Put the right check marks in the Log menu}
  709.  
  710.     procedure SetLogMenu;
  711.  
  712.     begin
  713.         CheckItem(logMenu, logEvents, reportEvents);
  714.         CheckItem(logMenu, excludeLWind, excludeLog);
  715.         CheckItem(logMenu, wrapStyle, logWrap >= 0);
  716.         CheckItem(logMenu, leftJust, logJust = teJustLeft);
  717.         CheckItem(logMenu, centerJust, logjust = teJustCenter);
  718.         CheckItem(logMenu, rightJust, logJust = teJustRight);
  719.         CheckItem(logMenu, small, logsize = 9);
  720.         CheckItem(logMenu, medium, logsize = 12);
  721.         CheckItem(logMenu, large, logSize = 24);
  722.     end;
  723.  
  724. {    Set display style of log window}
  725.  
  726.     procedure SetStyle;
  727.  
  728.     begin
  729.         SetDWindowStyle(logWind, logFont, logSize, logWrap, logJust);
  730.         SetLogMenu;
  731.     end;
  732.  
  733. {    Log menu handler}
  734.  
  735.     procedure DoLogMenu (item: integer);
  736.  
  737.     begin
  738.         case item of
  739.             logEvents: 
  740.                 begin
  741.                     reportEvents := not reportEvents;
  742.                     SetLogMenu;
  743.                 end;
  744.             excludeLWind: 
  745.                 begin
  746.                     excludeLog := not excludeLog;
  747.                     SetLogMenu;
  748.                 end;
  749.             flushLog: 
  750.                 FlushDWindow(logWind, longint(32767));
  751.             wrapStyle: 
  752.                 begin
  753.                     if logWrap >= 0 then
  754.                         logWrap := -1
  755.                     else
  756.                         logWrap := 0;
  757.                     SetStyle;
  758.                 end;
  759.             leftJust: 
  760.                 begin
  761.                     logJust := teJustLeft;
  762.                     SetStyle;
  763.                 end;
  764.             centerJust: 
  765.                 begin
  766.                     logJust := teJustCenter;
  767.                     SetStyle;
  768.                 end;
  769.             rightJust: 
  770.                 begin
  771.                     logJust := teJustRight;
  772.                     SetStyle;
  773.                 end;
  774.             small: 
  775.                 begin
  776.                     logFont := monaco;
  777.                     logSize := 9;
  778.                     SetStyle;
  779.                 end;
  780.             medium: 
  781.                 begin
  782.                     logFont := systemFont;
  783.                     logSize := 12;
  784.                     SetStyle;
  785.                 end;
  786.             large: 
  787.                 begin
  788.                     logFont := geneva;
  789.                     logSize := 24;
  790.                     SetStyle;
  791.                 end;
  792.             top: 
  793.                 SetDWindowPos(logWind, 0);
  794.             bottom: 
  795.                 SetDWindowPos(logWind, 32767);
  796.             otherwise
  797.         end;
  798.     end;
  799.  
  800. {    Handle selection of About… item from Apple menu}
  801.  
  802.     procedure DoAbout;
  803.  
  804.         var
  805.             ignore: integer;
  806.  
  807.     begin
  808.         ignore := Alert(aboutAlrtRes, nil);
  809.     end;
  810.  
  811. {    Dispose of event selection window (and controls)}
  812.  
  813.     procedure WClobber;
  814.  
  815.     begin
  816.         DisposeWindow(selectWind);
  817.     end;
  818.  
  819. {    Create controls}
  820.  
  821.     procedure MakeControls (theWind: windowPtr);
  822.  
  823.         var
  824.             i: integer;
  825.             ci: CtrlInfoPtr;
  826.             r: Rect;
  827.             genericPtr: booleanPtr;
  828.  
  829.     begin
  830.         for i := 0 to maxButton - 1 do
  831.             begin
  832.                 ci := @ctrlInfo[i];
  833.                 SetRect(r, ci^.loc.h, ci^.loc.v, ci^.loc.h + StringWidth(ci^.title) + 30, ci^.loc.v + 20);
  834.                 genericPtr := ci^.flagAddr;
  835.                 ci^.ctrl := NewControl(theWind, r, ci^.title, true, integer(genericPtr^), 0, 1, checkBoxProc, longint(ci));
  836.             end;
  837.         ValidRect(theWind^.portRect);
  838.     end;
  839.  
  840. begin
  841.     SetupStuff;
  842.     SkelInit(6, nil);
  843.     TransDisplayInit;
  844.     SkelApple('About EventLog...', @DoAbout);
  845.     fileMenu := GetMenu(fileMenuRes);
  846.     dummy := SkelMenu(fileMenu, @DoFileMenu, nil, false);
  847.  
  848.     editMenu := GetMenu(editMenuRes);
  849.     DisableItem(editmenu, 0);
  850.     dummy := SkelMenu(editMenu, nil, nil, false);
  851.  
  852.     logMenu := GetMenu(logMenuRes);
  853.     dummy := Skelmenu(logMenu, @DoLogmenu, nil, true);
  854.  
  855. {    Create windows and install handlers.}
  856.  
  857.     SetDwindowNotify(nil, @Activate);
  858.  
  859.     helpWind := GetNEwDWindow(helpWindRes, WindowPtr(-1));
  860.     SetDWindowStyle(helpWind, 0, 0, 0, teJustLeft);
  861.  
  862.     h := GetREsource('TEXT', helpTextRes);    { read help text }
  863.     HLock(h);                            { lock it and write to window }
  864.     DisplayText(h^, GetHandleSize(h));
  865.     HUnlock(h);
  866.     ReleaseResource(h);                { done with it, so goodbye }
  867.     SetDWindowPos(helpWind, 0);        { scroll back to top }
  868.     ShowWindow(helpWind);
  869.  
  870.     logWind := GetNewDWindow(logWindRes, WindowPtr(-1));
  871.  
  872.     SkelEventHook(@logEvent);
  873.     reportEvents := true;
  874.     excludeLog := false;
  875.  
  876.     logFont := monaco;
  877.     logSize := 9;
  878.     logWrap := 0;
  879.     logJust := teJustLeft;
  880.     SetStyle;
  881.     ShowWindow(logWind);
  882.  
  883.     selectWind := GetNewWindow(selectWindRes, nil, WindowPtr(-1));
  884.  
  885.     dummy := SkelWindow(selectWind, @Mouse, nil, @Update, @Activate, nil, @WClobber, nil, true);
  886.         { the window }
  887.         { mouse click handler }
  888.         { key clicks are ignored }
  889.         { window updating procedure }
  890.         { window activate/deactivate procedure }
  891.         { hide window }
  892.         { window disposal procedure }
  893.         { idle proc }
  894.         { irrelevant }
  895.  
  896.     MakeControls(selectWind);
  897.  
  898. {    Process events until user quits,}
  899. {    then clean up and exit}
  900.  
  901.     CheckFront;
  902.     SelectWindow(HelpWind);
  903.     SkelBackground(@CheckFront);
  904.     SkelMain;
  905.     SkelClobber;
  906. end.